Skip to main content

C4 Model

The C4 model is a way of drawing software architecture at four levels of detail, so that each diagram has one audience and one purpose. It was created by Simon Brown and is deliberately informal — there is no compliance to achieve.

It earns its place in health architecture because the alternative, in practice, is a single diagram containing forty boxes that nobody can read and nobody maintains.

LevelShowsAudience
1 — System contextYour system, its users, and the systems it talks toEveryone, including non-technical stakeholders
2 — ContainerThe deployable/runnable pieces inside it and how they communicateArchitects, developers, operations
3 — ComponentThe major structural pieces inside one containerDevelopers working on that container
4 — CodeClasses, schemas — usually generated, rarely drawnOccasionally useful, often skipped

Most health architecture work lives at levels 1 and 2. Level 3 is worth drawing for the one or two containers that are genuinely complex. Level 4 is almost always a waste of effort — generate it if you need it.


Level 1 — System context​

One box for your system, surrounded by the people and systems it interacts with. No internals.

Example: an antenatal care EMR

┌────────────┐ ┌──────────────────┐
│ Midwife │ │ Programme │
│ (facility)│ │ manager (dist.) │
└─────┬──────┘ └────────┬─────────┘
│ records ANC contact │ reviews coverage
▼ ▼
┌───────────────────────────────────────────┐
│ ANC EMR system │
│ Registers pregnancies, records contacts, │
│ schedules follow-up, flags danger signs │
└───┬───────────┬──────────────┬────────────┘
│ │ │
│ patient │ aggregate │ lab orders
│ identity │ indicators │ + results
▼ ▼ ▼
┌────────────┐ ┌─────────┐ ┌──────────────┐
│ Client │ │ DHIS2 │ │ Laboratory │
│ Registry │ │ (HMIS) │ │ system │
└────────────┘ └─────────┘ └──────────────┘

The value of this diagram is political as much as technical: it makes visible that the EMR does not own patient identity, and that someone must therefore operate a client registry.


Level 2 — Container​

"Container" here means a separately runnable thing — an application, a service, a database, a message broker. Not necessarily a Docker container, though it often is one.

Example: a national health information exchange

Point-of-service systems (EMR, LMIS, CHW app, lab)
│ HTTPS / FHIR, HL7 v2
▼
┌──────────────────────────────────────────────────────┐
│ Interoperability layer │
│ ┌────────────────┐ ┌──────────────┐ │
│ │ API gateway │→ │ Mediators │ │
│ │ authN/authZ, │ │ transform, │ │
│ │ routing, audit │ │ orchestrate │ │
│ └───────┬────────┘ └──────┬───────┘ │
│ │ │ │
│ ┌───────▼──────┐ ┌──────▼───────┐ │
│ │ Audit store │ │ Message queue│ │
│ └──────────────┘ └──────────────┘ │
└───────┬───────────────┬──────────────┬───────────────┘
▼ ▼ ▼
┌──────────────┐ ┌─────────────┐ ┌──────────────────┐
│ Client │ │ Facility │ │ Terminology │
│ registry │ │ registry │ │ service │
│ + its DB │ │ + its DB │ │ + its DB │
└──────────────┘ └─────────────┘ └──────────────────┘
│
▼
┌──────────────────────────┐ ┌──────────────────┐
│ Shared health record │──▶│ Analytics / │
│ (FHIR server + DB) │ │ data warehouse │
└──────────────────────────┘ └──────────────────┘

Annotate each arrow with protocol, format and direction — HTTPS / FHIR R4 Bundle, synchronous is a useful label; an unlabelled arrow is decoration.

Compare with the component structure in OpenHIE: the C4 container diagram is where a reference architecture becomes a deployable design.


Level 3 — Component​

Inside one container. Draw this only where the internal structure is a real design decision.

Example: inside the client registry

┌──────────────────────────────────────────────────┐
│ Client registry │
│ │
│ ┌───────────────┐ ┌────────────────────────┐ │
│ │ FHIR API │──▶│ Matching engine │ │
│ │ Patient, │ │ deterministic rules + │ │
│ │ $match │ │ probabilistic scoring │ │
│ └───────────────┘ └───────────┬────────────┘ │
│ │ │
│ ┌─────────────────────────┼────────────┐ │
│ ▼ ▼ ▼ │
│ ┌───────────┐ ┌──────────────┐ ┌───────────┐
│ │ Golden │ │ Review queue │ │ Link/ │
│ │ record │ │ (human │ │ unlink │
│ │ store │ │ adjudication)│ │ audit log│
│ └───────────┘ └──────────────┘ └───────────┘
└──────────────────────────────────────────────────┘

The review queue is the component people forget, and the reason MPI projects stall.


Level 4 — Code​

Class or schema diagrams. Generate from the source; do not maintain by hand.


Supplementary diagrams​

C4 is often paired with three others:

  • Deployment diagram — mapping containers onto infrastructure (nodes, regions, networks). Essential for availability and data residency conversations.
  • Sequence diagram — for a single interaction over time. The clearest way to explain a SMART on FHIR launch or a patient-identity lookup.
  • Data flow diagram — what personal data moves where, which is the input to a privacy impact assessment.

Applying C4 across the ecosystem​

SystemLevel 1 showsLevel 2 shows
EMRClinicians, patients, lab, HIE, HMISWeb app, API, database, integration adapter
HIEAll point-of-service systems, registries, regulatorGateway, mediators, queue, audit, registries
FHIR platformClient apps, identity provider, source systemsFHIR server, terminology server, auth server, storage
DHIS2Facilities, districts, programmes, ministryWeb app, analytics tables, database, import/export
National platformMinistry, provinces, citizens, other government sectorsShared services (identity, exchange, registries, consent)
AI platformClinicians, data stewards, model ownersInference service, model registry, feature/vector store, monitoring, audit

Practical rules​

  1. Every diagram gets a title, a legend and a date. An undated architecture diagram is folklore.
  2. One level per diagram. Mixing containers and components is the most common way these become unreadable.
  3. Keep the notation boring. Boxes, arrows, labels. Colour carries at most one meaning, stated in the legend.
  4. Diagram what exists and what is proposed as separate diagrams, clearly labelled. Merging them is how a roadmap gets mistaken for a system.
  5. Store diagrams as text where possible — Mermaid, PlantUML or Structurizr DSL — so they diff in version control alongside the ADR that explains them.

Tooling​

ToolNotes
StructurizrC4-native, diagrams-as-code from a single model
PlantUML (+ C4-PlantUML macros)Text-based, renders anywhere, no service dependency
MermaidRenders natively in GitHub and many docs sites; simplest to sustain
draw.io / diagrams.netFree-form; easiest for people who will not write DSL

Choose the one your team will actually update six months from now. That is the only criterion that matters.


References​